/*******************************************************************************
 * Copyright (c) 2006 CEA List.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     CEA List - initial API and implementation
 *******************************************************************************/
package com.cea.papyrus.diagram.usecase.figure;

import org.eclipse.draw2d.Figure;
import org.eclipse.draw2d.Graphics;
import org.eclipse.draw2d.ToolbarLayout;
import org.eclipse.draw2d.geometry.Point;
import org.eclipse.draw2d.geometry.Rectangle;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.FontData;
import org.eclipse.uml2.uml.Element;

import com.cea.papyrus.core.PapyrusPlugin;
import com.cea.papyrus.core.figures.NodeFigure;
import com.cea.papyrus.core.utils.Debug;
import com.cea.papyrus.diagraminterchange2.di2.GraphElement;

/**
 * Defines the view of a use case displayed as an ellipse
 * with its extension points.
 * 
 * @author Gilles Cannenterre
 * @since 9 oct. 06
 */
public class UseCaseEllipseFormWithExtensionPointsFigure extends UseCaseEllipseGeneralFigure {

	/**
	 * The Class UseCaseBorderFigure.
	 * Holds the border line in the ellipse.
	 */
	protected class UseCaseBorderFigure extends Figure {
				
				/**
				 * The Constructor.
				 */
				public UseCaseBorderFigure() {
					super();
				}
			
				/**
				 * setBound is called to resize or move graphical Element by Eclipse
				 * In the case of this package we have to call setDimension Before.
				 * 
				 * @param rect coordinate of the contentPackage.
				 */
				@Override
				public void setBounds(Rectangle rect) {	
			
					int borderHeight = 1;
					int borderWidth  = rect.width;
			
					Rectangle borderRect = new Rectangle();
					borderRect.setLocation(0, (int)getParent().getSize().height/ 3);
					borderRect.setSize(borderWidth, borderHeight);
			
					super.setBounds(borderRect);
			
					Debug.debug(this," bounds are : " +getBounds(), channel);
				}
			
				/**
				 * Paint figure.
				 * 
				 * @param graphics the graphics
				 */
				@Override
				public void paintFigure(Graphics graphics){	
					// Attach a line on the ellipse without using EllipseAnchor.
					double b = getParent().getBounds().height / 2;								
					if (b > 0 ){
						Point center = getParent().getBounds().getCenter();	
						center.x = center.x - getParent().getBounds().x;
						center.y = (int)getParent().getSize().height / 2;
						double a = getParent().getBounds().width / 2;
						double y = getBounds().y;
						double xLeft = - Math.sqrt((a*a)-(((a*a)/(b*b))*(y-center.y)*(y-center.y))) - 1;
						double xRight = -xLeft - 3;				
						graphics.drawLine((int)(center.x+xLeft),(int)y,(int)(center.x+xRight),(int)y);
					}
				}
			}

	/**
	 * The Class UseCaseContainerFigure.
	 * Holds the extension points.
	 */
	protected class UseCaseContainerFigure extends Figure {
	
		/**
		 * The Constructor.
		 */
		public UseCaseContainerFigure() {
			super();
			Debug.debug(this, "ContainerFigure()", channel);
			ToolbarLayout layout = new ToolbarLayout(ToolbarLayout.VERTICAL); // vertically
			layout.setMinorAlignment(ToolbarLayout.ALIGN_CENTER);
			layout.setSpacing(2);
			setLayoutManager(layout);
		}
	
		/**
		 * Paint border.
		 * 
		 * @param graphics the graphics
		 */
		@Override
		public void paintBorder(Graphics graphics) {	
		}
	
		/**
		 * Sets the bounds.
		 * 
		 * @param rect the rect
		 */
		@Override
		public void setBounds(Rectangle rect) {
			Debug.debug(this, "setBounds(Rectangle)", channel);
			
			int fatherHeight = getParent().getSize().height;
			
			Rectangle containerRect = new Rectangle();
			containerRect.setLocation(0, (int) (fatherHeight/3) + borderFigure.getSize().height + containerLabelFigure.getSize().height);
			containerRect.setSize(rect.width, (int)((fatherHeight - borderFigure.getSize().height - containerLabelFigure.getSize().height) / 2));
			
			super.setBounds(containerRect);
			
			Debug.debug(this," bounds are : " +getBounds(), channel);
		}	
	}

	/**
	 * The Class UseCaseContainerLabelFigure.
	 */
	protected class UseCaseContainerLabelFigure extends NodeFigure {
		
		/**
		 * The Constructor.
		 */
		public UseCaseContainerLabelFigure() {
			super();
			ToolbarLayout layout = new ToolbarLayout(ToolbarLayout.VERTICAL); // vertically
			layout.setStretchMinorAxis(true);
			layout.setMinorAlignment(ToolbarLayout.ALIGN_TOPLEFT);
			layout.setSpacing(2);
			setLayoutManager(layout);
		}
	
		/**
		 * setBound is called to resize or move graphical Element by Eclipse
		 * In the case of this package we have to call setDimension Before.
		 * 
		 * @param rect coordinate of the contentPackage.
		 */
		@Override
		public void setBounds(Rectangle rect) {
	
			int headerHeight = 20;
			int headerWidth  = rect.width;
	
			Rectangle containerLabelRect = new Rectangle();
			containerLabelRect.setLocation(0, (int)(getParent().getSize().height/3) + borderFigure.getSize().height);
			containerLabelRect.setSize(headerWidth, headerHeight);
	
			super.setBounds(containerLabelRect);
	
			Debug.debug(this," bounds are : " +getBounds(), channel);
		}
	
		/**
		 * Paint border.
		 * 
		 * @param graphics the graphics
		 */
		@Override
		public void paintBorder(Graphics graphics){			
		}
	
		/**
		 * Paint figure.
		 * 
		 * @param graphics the graphics
		 */
		@Override
		public void paintFigure(Graphics graphics) {
		
		}
	}

	/**
	 * The border figure.
	 */
	protected UseCaseBorderFigure borderFigure;

	/**
	 * The container label figure.
	 */
	protected UseCaseContainerLabelFigure containerLabelFigure;

	/**
	 * The Constructor.
	 */
	public UseCaseEllipseFormWithExtensionPointsFigure() {
		super();
		ToolbarLayout layout = new ToolbarLayout();
		setLayoutManager(layout);
		borderFigure = new UseCaseBorderFigure();
		add(borderFigure);
		containerLabelFigure = new UseCaseContainerLabelFigure();
		containerLabelFigure.setName("extensions points");
		add(containerLabelFigure);
		containerFigure = new UseCaseContainerFigure();
		add(containerFigure);
	}

	/**
	 * Paint border.
	 * 
	 * @param graphics the graphics
	 */
	@Override
	public void paintBorder(Graphics graphics) {

	}

	/**
	 * Sets the bounds of the figure and its children.
	 * 
	 * @param rect the rect
	 */
	@Override
	public void setBounds(Rectangle rect) {
		Debug.debug(this, "setBounds(Rectangle)", channel);
		//  BorderFigure
		borderFigure.setBounds(new Rectangle(rect));
		// ContainerLabelFigure
		containerLabelFigure.setBounds(new Rectangle(rect));
		super.setBounds(rect);
	}

	/**
	 * Sets the name.
	 * 
	 * @param name the name
	 */
	@Override
	public void setName(String name) {}

	/**
	 * Sets the qualified name.
	 * 
	 * @param qualifiedName the qualified name
	 */
	@Override
	public void setQualifiedName(String qualifiedName) {}

	/**
	 * Sets the stereotypes.
	 * 
	 * @param stereotypes the stereotypes
	 */
	@Override
	public void setStereotypes(String stereotypes) {}

	/**
	 * Refresh colors.
	 * 
	 * @param graphElement the graph element
	 */
	@Override
	public void refreshColors(GraphElement graphElement) {
		super.refreshColors(graphElement);
		
		Font baseFont = super.getNameLabel().getFont();
		if (baseFont.getFontData() != null){
			FontData baseFontData = baseFont.getFontData()[0];
			FontData[] labelFontData={new FontData(baseFontData.getName(), baseFontData.getHeight(), SWT.BOLD)};
			Font labelFont = PapyrusPlugin.fontManager.get(labelFontData);			
			containerLabelFigure.setFont(labelFont);
		}
		
		containerLabelFigure.setBackgroundColor(getBackgroundColor());
		containerLabelFigure.setFontColor(getFontColor());
		containerLabelFigure.setBorderColor(getBorderColor());
		containerLabelFigure.setForeGroundColor(getForeGroundColor());
		
		borderFigure.setForegroundColor(getBorderColor());
		setForegroundColor(getBorderColor());
	}

	/**
	 * Paint figure.
	 * 
	 * @param graphics the graphics
	 */
	@Override
	public void paintFigure(Graphics graphics) {
		graphics.setAntialias(SWT.ON);
		Rectangle rect = getBounds();
		graphics.fillOval(new Rectangle(rect.x, rect.y + 1, rect.width - 2,
				getSize().height - 2));
		graphics.setLineWidth(1);
		graphics.drawOval(new Rectangle(rect.x, rect.y + 1, rect.width - 2,
				getSize().height - 2));
	}

	/**
	 * Refresh presentation.
	 * 
	 * @param presentation the presentation
	 * @param selection the selection
	 */
	@Override
	public void refreshPresentation(String presentation, Element selection, GraphElement ge) {}

	/**
	 * Use local coordinates.
	 * 
	 * @return true, if use local coordinates
	 */
	@Override
	protected boolean useLocalCoordinates(){return true;}
}